package cn.yunbamboos.rest.service.transaction;

import cn.yunbamboos.rest.service.IRestService;
import jakarta.annotation.Resource;
import org.springframework.jdbc.datasource.DataSourceTransactionManager;
import org.springframework.stereotype.Component;
import org.springframework.transaction.TransactionStatus;
import org.springframework.transaction.support.DefaultTransactionDefinition;

/**
 * 默认的服务事务管理实现
 */
public class DefaultServiceTransactionManager extends BaseServiceTransactionManager {

    private final ThreadLocal<ServiceTransactionStatus> local = new ThreadLocal<>();

    private final DataSourceTransactionManager dataSourceTransactionManager;
    private final DefaultTransactionDefinition transactionDefinition;

    public DefaultServiceTransactionManager(DataSourceTransactionManager dataSourceTransactionManager, DefaultTransactionDefinition transactionDefinition) {
        this.dataSourceTransactionManager = dataSourceTransactionManager;
        this.transactionDefinition = transactionDefinition;
    }

    @Override
    public void beginService(IRestService service) {
        Transaction transaction = service.transaction();
        if (transaction.equals(Transaction.READ)) {
            transactionDefinition.setReadOnly(true); // 设置只读事务
            TransactionStatus transactionStatus = dataSourceTransactionManager.getTransaction(transactionDefinition);
            local.set(new ServiceTransactionStatus(transactionStatus).begin());
        }
        if (transaction.equals(Transaction.WRITE)) {
            transactionDefinition.setReadOnly(false);
            TransactionStatus transactionStatus = dataSourceTransactionManager.getTransaction(transactionDefinition);
            local.set(new ServiceTransactionStatus(transactionStatus).begin());
        }
    }

    @Override
    public void commitService(IRestService service) {
        ServiceTransactionStatus status = local.get();
        if (status != null) {
            dataSourceTransactionManager.commit(status.getTransactionStatus());
            status.commit();
        }
    }

    @Override
    public void rollbackService(IRestService service) {
        ServiceTransactionStatus status = local.get();
        if (status != null) {
            dataSourceTransactionManager.rollback(status.getTransactionStatus());
            status.rollback();
        }
    }

    @Override
    public void releaseService(IRestService service) {
        local.remove();
    }

}
